1 package org.apache.maven.surefire.common.junit4;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 import org.apache.maven.surefire.report.ReportEntry;
23 import org.apache.maven.surefire.report.RunListener;
24 import org.apache.maven.surefire.report.SimpleReportEntry;
25 import org.apache.maven.surefire.report.StackTraceWriter;
26 import org.apache.maven.surefire.testset.TestSetFailedException;
27 import org.junit.runner.Description;
28 import org.junit.runner.Result;
29 import org.junit.runner.notification.Failure;
30
31 import java.util.regex.Matcher;
32 import java.util.regex.Pattern;
33
34
35
36
37
38 public class JUnit4RunListener
39 extends org.junit.runner.notification.RunListener
40 {
41 private static final Pattern PARENS = Pattern.compile( "^" + ".+"
42 + "\\(("
43
44 + "[^\\\\(\\\\)]+"
45 + ")\\)" + "$" );
46
47 protected final RunListener reporter;
48
49
50
51
52
53 private final ThreadLocal<Boolean> failureFlag = new InheritableThreadLocal<Boolean>();
54
55 private final JUnit4Reflector jUnit4Reflector = new JUnit4Reflector();
56
57
58
59
60
61
62 public JUnit4RunListener( RunListener reporter )
63 {
64 this.reporter = reporter;
65 }
66
67
68
69
70
71
72
73
74 public void testIgnored( Description description )
75 throws Exception
76 {
77 final String reason = jUnit4Reflector.getAnnotatedIgnoreValue( description );
78 final SimpleReportEntry report =
79 SimpleReportEntry.ignored( getClassName( description ), description.getDisplayName(), reason );
80 reporter.testSkipped( report );
81 }
82
83
84
85
86
87
88 public void testStarted( Description description )
89 throws Exception
90 {
91 reporter.testStarting( createReportEntry( description ) );
92 failureFlag.remove();
93 }
94
95
96
97
98
99
100 @SuppressWarnings( { "ThrowableResultOfMethodCallIgnored" } )
101 public void testFailure( Failure failure )
102 throws Exception
103 {
104 String testHeader = failure.getTestHeader();
105 if ( isInsaneJunitNullString( testHeader ) )
106 {
107 testHeader = "Failure when constructing test";
108 }
109 ReportEntry report = SimpleReportEntry.withException( getClassName( failure.getDescription() ), testHeader,
110 createStackTraceWriter( failure ) );
111
112 if ( failure.getException() instanceof AssertionError )
113 {
114 this.reporter.testFailed( report );
115 }
116 else
117 {
118 this.reporter.testError( report );
119 }
120 failureFlag.set( Boolean.TRUE );
121 }
122
123 protected StackTraceWriter createStackTraceWriter( Failure failure )
124 {
125 return new JUnit4StackTraceWriter( failure );
126 }
127
128 @SuppressWarnings( { "UnusedDeclaration" } )
129 public void testAssumptionFailure( Failure failure )
130 {
131 this.reporter.testAssumptionFailure( createReportEntry( failure.getDescription() ) );
132 failureFlag.set( Boolean.TRUE );
133 }
134
135
136
137
138
139
140
141 public void testFinished( Description description )
142 throws Exception
143 {
144 Boolean failure = failureFlag.get();
145 if ( failure == null )
146 {
147 reporter.testSucceeded( createReportEntry( description ) );
148 }
149 }
150
151 protected SimpleReportEntry createReportEntry( Description description )
152 {
153 return new SimpleReportEntry( getClassName( description ), description.getDisplayName() );
154 }
155
156 public String getClassName( Description description )
157 {
158 String name = extractClassName( description );
159 if ( name == null || isInsaneJunitNullString( name ) )
160 {
161
162 Description subDescription = description.getChildren().get( 0 );
163 if ( subDescription != null )
164 {
165 name = extractClassName( subDescription );
166 }
167 if ( name == null )
168 {
169 name = "Test Instantiation Error";
170 }
171 }
172 return name;
173 }
174
175 private boolean isInsaneJunitNullString( String value )
176 {
177 return "null".equals( value );
178 }
179
180 public static String extractClassName( Description description )
181 {
182 String displayName = description.getDisplayName();
183 Matcher m = PARENS.matcher( displayName );
184 if ( !m.find() )
185 {
186 return displayName;
187 }
188 return m.group( 1 );
189 }
190
191 public static String extractMethodName( Description description )
192 {
193 String displayName = description.getDisplayName();
194 int i = displayName.indexOf( "(" );
195 if ( i >= 0 )
196 {
197 return displayName.substring( 0, i );
198 }
199 return displayName;
200 }
201
202
203 public static void rethrowAnyTestMechanismFailures( Result run )
204 throws TestSetFailedException
205 {
206 if ( run.getFailureCount() > 0 )
207 {
208 for ( Failure failure : run.getFailures() )
209 {
210 if ( isFailureInsideJUnitItself( failure ) )
211 {
212 final Throwable exception = failure.getException();
213 throw new TestSetFailedException( exception );
214 }
215 }
216 }
217 }
218
219 public static boolean isFailureInsideJUnitItself( Failure failure )
220 {
221 return failure.getDescription().getDisplayName().equals( "Test mechanism" );
222 }
223 }